/* 
 * This file is part of the Coffee Survey Framework - http://coffee.codeplex.com
 */
using System;
using System.Xml;
using System.Collections.Generic;
using Coffee.ServiceLocators;
using System.Text.RegularExpressions;

namespace Coffee
{
    /// <summary>
    /// Contains methods used for parsing the Survey Definition file
    /// </summary>
    public class Parser
    {
        /// <summary>
        /// Helper function for calling SelectNode with a namespace
        /// </summary>
        /// <param name="el"></param>
        /// <param name="path"></param>
        /// <returns></returns>
        public static XmlNodeList SelectNodes(XmlNode el, string defaultnamespace, string path)
        {
            XmlNamespaceManager nsmgr = new XmlNamespaceManager(el.OwnerDocument.NameTable);
            nsmgr.AddNamespace(defaultnamespace, el.OwnerDocument.DocumentElement.NamespaceURI);
            return el.SelectNodes(path, nsmgr);
        }

        /// <summary>
        /// Helper function for calling SelectSingleNode with a namespace
        /// </summary>
        /// <param name="el"></param>
        /// <param name="path"></param>
        /// <returns></returns>
        public static XmlNode SelectSingleNode(XmlNode el, string defaultnamespace, string path)
        {
            XmlNamespaceManager nsmgr = new XmlNamespaceManager(el.OwnerDocument.NameTable);
            nsmgr.AddNamespace(defaultnamespace, el.OwnerDocument.DocumentElement.NamespaceURI);
            return el.SelectSingleNode(path, nsmgr);
        }

        public static object ParseValue(XmlNode node)
        {
            return ParseValue(node, null);
        }

        public static object ParseValue(XmlNode node, string src)
        {
            string text = null;
            if (node.Attributes["src"] != null)
            {
                src = node.Attributes["src"].Value;
            }
            text = node.SelectSingleNode("text()").Value;
            
            Match m = Regex.Match(text, "^([\\W])(.*)$");
            if (m.Success)
            {
                src = m.Groups[1].Value;
                text = m.Groups[2].Value;
            }

            if (src != null)
            {
                ValueParserDelegate parser = ValueParserService.ResolveProvider(src);
                if (parser != null)
                    return parser(text);
                else
                    return text;
            }
            return text;
        }

        internal static List<String> ParseParameters(string paramlist)
        {
            List<String> list = new List<string>();
            int ptr = 0;
            while (ptr < paramlist.Length)
            {
                string param;
                if (paramlist.Substring(ptr, 1) == "\"")
                {
                    param = paramlist.Substring(ptr + 1, paramlist.IndexOf("\"", ptr + 1) - 1);
                    ptr += param.Length + 2;
                }
                else
                {
                    param = paramlist.Substring(ptr + 1, paramlist.IndexOf(",", ptr + 1) - 1);
                    ptr += param.Length + 1;
                }
                list.Add(param);

            }
            return list;
        }

        public static string GetIDPath(XmlNode node)
        {
            string path = "";
            while ((node != null) && (node.Name != "#document"))
            {
                XmlAttribute id = node.Attributes["id"];
                if (id != null) path = id.Value + "_" + path;
                node = node.ParentNode;
            }

            return path;
        }

    }
}